package com.dungeon.game;

import java.util.ArrayList;
import java.util.Collections;
import java.util.Comparator;

import android.app.Activity;
import android.app.AlertDialog;
import android.app.Service;
import android.content.Context;
import android.content.DialogInterface;
import android.graphics.Color;
import android.graphics.Typeface;
import android.graphics.drawable.BitmapDrawable;
import android.os.Bundle;
import android.text.InputType;
import android.view.Gravity;
import android.view.View;
import android.view.inputmethod.InputMethodManager;
import android.widget.Button;
import android.widget.EditText;
import android.widget.ImageView;
import android.widget.LinearLayout;
import android.widget.LinearLayout.LayoutParams;
import android.widget.RelativeLayout;
import android.widget.ScrollView;
import android.widget.TextView;

import com.dungeon.game.Constants.Character_action_code;
import com.dungeon.game.Constants.Class_code;
import com.dungeon.game.Constants.Equipment_type_code;
import com.dungeon.game.Constants.Potion_type;
import com.dungeon.game.Constants.Scenario_code;
import com.dungeon.game.Constants.Shopping_code;
import com.dungeon.game.Constants.Trinket_type_code;

public class CharsheetDialog extends Activity {

	ScrollView scroll;
	LinearLayout ll,eq;
	Charsheet cs;
	TextView title;
	ImageView pic;
	Button ok_button;
	EditText et;
	InputMethodManager imm;

	protected void onCreate(Bundle savedInstanceState) {
		super.onCreate(savedInstanceState);
        imm = (InputMethodManager)getSystemService(Service.INPUT_METHOD_SERVICE);
		cs = Campaignstate.chars.get(getIntent().getIntExtra("char_number", -1));
		setContentView(R.layout.activity_charsheet_dialog);
		scroll = (ScrollView)findViewById(R.id.charsheet_dialog_ScrollView1);
		ll = (LinearLayout)findViewById(R.id.charsheet_dialog_ll);
		title = (TextView)findViewById(R.id.charsheet_dialog_title);
		title.setText(cs.name);
		pic = (ImageView)findViewById(R.id.charsheet_dialog_image);
		pic.setImageBitmap(LaunchActivity.gi.getImageBasic(cs.image));
		make_ll(null,null,false,null,null);
        ok_button = (Button)findViewById(R.id.charsheet_dialog_ok);
        ok_button.setText("OK");
        ok_button.setTextColor(Color.BLACK);
        ok_button.setTextSize(16);
        ok_button.setOnClickListener(new EndListener(this));
    }

	void make_ll(Character_action_code ca,Item i,boolean is_from_stash,Potion_type p,Integer trinket_no_to_drop){
		if (ca!=null){
	    	cs.master_action_codes.add(ca);
	    	Character_action a = Campaignstate.ca.make_action(ca);
	    	ArrayList<Character_action_code> to_remove = new ArrayList<Character_action_code>();
	    	for (Character_action_code ca2 : cs.master_action_codes){
	    		if (a.obsoletes().contains(ca2))
	    			to_remove.add(ca2);
	    	}
			for (Character_action_code ca2 : to_remove){
				cs.obsoleted_actions.add(ca2);
				cs.master_action_codes.remove(ca2);
			}
		}
		if (i!=null){
			if (is_from_stash){
				Campaignstate.items_owned.remove(i);
			} else {
				Campaignstate.gold = Campaignstate.gold - i.cost();
			}
			if (i.is_melee_weapon()){
				if (cs.melee_weapon!=null)
					Campaignstate.items_owned.add(cs.melee_weapon);
				cs.melee_weapon = i;
				if (i.two_handed()){
					if (cs.offhand!=null)
						Campaignstate.items_owned.add(cs.offhand);
					cs.offhand = null;
				}
			}
			if (i.is_missile_weapon()){
				if (cs.missile_weapon!=null)
					Campaignstate.items_owned.add(cs.missile_weapon);
				cs.missile_weapon = i;
			}
			if (i.is_offhand()){
				if (cs.offhand!=null)
					Campaignstate.items_owned.add(cs.offhand);
				cs.offhand = i;
				if (cs.melee_weapon!=null && cs.melee_weapon.two_handed()){
					if (cs.melee_weapon!=null)
						Campaignstate.items_owned.add(cs.melee_weapon);
					cs.melee_weapon = null;
				}
			}
			if (i.is_armor()){
				if (cs.armor!=null)
					Campaignstate.items_owned.add(cs.armor);
				cs.armor = i;
			}
			if (i.is_trinket()){
				// if we are here, <=3 trinkets wielded
				Item to_remove = null;
				for (Item t : cs.trinkets){
					if (t!=null && t.trinket_type()!=null && t.trinket_type()==i.trinket_type()){
						to_remove = t;
						continue;
					}
				}
				if (to_remove!=null){
					cs.trinkets.remove(to_remove);
					Campaignstate.items_owned.add(to_remove);
				}
				cs.trinkets.add(i);
			}
		}
		if (p!=null){
			cs.potions.add(p);
			Character_action pca = Campaignstate.ca.make_action(p.get_character_action_code());
			int cost = pca.gold_cost();
			if (Campaignstate.victories.contains(Scenario_code.SC_DESERT)) cost=cost/5;
			Campaignstate.gold = Campaignstate.gold - cost;
		}
		if (trinket_no_to_drop!=null){
			if (cs.trinkets.size()>trinket_no_to_drop && cs.trinkets.get(trinket_no_to_drop)!=null){
				Item to_drop = cs.trinkets.get(trinket_no_to_drop);
				if (to_drop.action_codes().contains(Character_action_code.CA_APOTHECARY) && !cs.master_action_codes.contains(Character_action_code.CA_APOTHECARY)){
            		if (cs.potions.size()==4){
            			cs.potions.remove(cs.potions.get(3));
            		}
				}
				Campaignstate.items_owned.add(to_drop);
				cs.trinkets.remove(to_drop);
			}
		}
    	ll.setBackgroundColor(Color.argb(0,0,0,0));
        ll.setGravity(Gravity.TOP);
        ll.removeAllViews();
        if (cs.level<6){
        	Button b_name = new Button(this);
            b_name.setText("Rename this character?");
            NameListener myhandler_n = new NameListener(this,cs);
            b_name.setOnClickListener(myhandler_n);
            ll.addView(b_name);
        }
        if (Campaignstate.rebuilds>0 && cs.genesis.equals("Has been with you since the beginning of the game.")){
        	if (cs.stat1+cs.stat2+cs.reflexes+cs.constitution+cs.intelligence+cs.stamina <= 20){
            	Button b_restat = new Button(this);
                b_restat.setText("Upgrade this character?");
                RestatListener myhandler_rs = new RestatListener(this,cs);
                b_restat.setOnClickListener(myhandler_rs);
                ll.addView(b_restat);
        	}
        }
        ll.addView(onetext(this,cs.genesis));
        ll.addView(heading(this,"Advancement"));
        ll.addView(onetext(this,"L"+cs.level+" "+Constants.class_code_to_name.get(cs.class_code)));
        ll.addView(twotext(this,"XP:",cs.xp));
        ll.addView(twotext(this,"Needed for next level:",Charsheet.xp_needed_for_level(cs.level+1)));
        ll.addView(twotext(this,"Recovery cost:",LaunchActivity.rez_cost(cs) + " gold"));
        ll.addView(heading(this,"Stats"));
        if (cs.class_code==Class_code.C_WARRIOR){
        	ll.addView(twotext(this,"Strength:",cs.stat1));
        	ll.addView(twotext(this,"Skill:",cs.stat2));
        } else if (cs.class_code==Class_code.C_ROGUE){
        	ll.addView(twotext(this,"Daring:",cs.stat1));
        	ll.addView(twotext(this,"Cunning:",cs.stat2));
        } else if (cs.class_code==Class_code.C_PRIEST){
        	ll.addView(twotext(this,"Valor:",cs.stat1));
        	ll.addView(twotext(this,"Wisdom:",cs.stat2));
        } else if (cs.class_code==Class_code.C_MAGE){
        	ll.addView(twotext(this,"Power:",cs.stat1));
        	ll.addView(twotext(this,"Subtlety:",cs.stat2));
        }
        ll.addView(twotext(this,"Constitution:",cs.constitution));
        ll.addView(twotext(this,"Energy:",cs.stamina));
        ll.addView(twotext(this,"Reflexes:",cs.reflexes));
        ll.addView(twotext(this,"Training:",cs.intelligence));
        ll.addView(heading(this,"Abilities"));
        LinearLayout ll_abilities = new LinearLayout(this);
        ll_abilities.setBackgroundColor(Color.argb(0,0,0,0));
        ll_abilities.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.WRAP_CONTENT));
        ll_abilities.setOrientation(LinearLayout.VERTICAL);
        ll_abilities.setGravity(Gravity.TOP);
        int remaining_actions = cs.get_n_skills();
        for (Character_action_code ac : cs.master_action_codes){
        	if (remaining_actions==0) continue;
        	remaining_actions = remaining_actions - 1;
        	Character_action a = Campaignstate.ca.make_action(ac);
        	ll_abilities.addView(twotext_firstitalic(this,a.name(),a.out_of_game_description()));
        }
        int actions_to_learn = cs.get_n_skills() - (cs.master_action_codes.size()+cs.obsoleted_actions.size());
        Button lb_shown = new Button(this);
        lb_shown.setText("Learn another action ("+actions_to_learn+")");
        View.OnClickListener myhandler1 = new View.OnClickListener() {
            public void onClick(View v) {
            	learn_dialog();
            }
          };
        lb_shown.setOnClickListener(myhandler1);
    	if (actions_to_learn>0)
    		ll_abilities.addView(lb_shown);
        Button respec = new Button(this);
        respec.setText("Respec ("+cs.respec_cost()+")");
        View.OnClickListener myhandler2 = new View.OnClickListener() {
            public void onClick(View v) {
            	if (cs.master_action_codes.contains(Character_action_code.CA_SLING) || cs.master_action_codes.contains(Character_action_code.CA_SHOOT) || cs.master_action_codes.contains(Character_action_code.CA_ZEN_ARCHER)){
    				if (cs.missile_weapon!=null){
    					Campaignstate.items_owned.add(cs.missile_weapon);
    					cs.missile_weapon = null;
    				}
            	}
            	if (cs.master_action_codes.contains(Character_action_code.CA_APOTHECARY)){
            		if (cs.potions.size()==4){
            			cs.potions.remove(cs.potions.get(3));
            		}
            	}
            	cs.master_action_codes = new ArrayList<Character_action_code>();
            	cs.obsoleted_actions = new ArrayList<Character_action_code>();
            	Campaignstate.gold = Campaignstate.gold - cs.respec_cost();
            	make_ll(null,null,false,null,null);
            	scroll.invalidate();
            	scroll.postInvalidate();
            }
          };
          respec.setOnClickListener(myhandler2);
    	if (cs.master_action_codes.size()>0 && Campaignstate.gold >= cs.respec_cost()){
    		ll_abilities.addView(respec);
    	} else if (Campaignstate.gold < cs.respec_cost()){
    		ll_abilities.addView(onetext(this,"It would cost you " + cs.respec_cost() + " gold to respec (i.e. forget your abilities and learn new ones)."));
    	}
        ll.addView(ll_abilities);
        ll.addView(heading(this,"Equipment"));
        ll.addView(horizontal_line());
        if (cs.melee_weapon!=null){
        	ll.addView(text_image_buybutton(this,cs,"Melee:",cs.melee_weapon.image,Shopping_code.SHOP_MAINHAND));
        	ll.addView(twotext(this, cs.melee_weapon.name(), cs.melee_weapon.description()));
        } else
        	ll.addView(twotext_buybutton(this,cs,"Melee:","None",Shopping_code.SHOP_MAINHAND));
        ll.addView(horizontal_line());
        if (cs.missile_weapon!=null){
        	ll.addView(text_image_buybutton(this,cs,"Missile:",cs.missile_weapon.image,Shopping_code.SHOP_SHOOTER));
        	ll.addView(twotext(this, cs.missile_weapon.name(), cs.missile_weapon.description()));
        } else
        	ll.addView(twotext_buybutton(this,cs,"Missile:","None",Shopping_code.SHOP_SHOOTER));
        ll.addView(horizontal_line());
        if (cs.offhand!=null){
        	ll.addView(text_image_buybutton(this,cs,"Offhand:",cs.offhand.image,Shopping_code.SHOP_OFFHAND));
        	ll.addView(twotext(this, cs.offhand.name(), cs.offhand.description()));
        } else
        	ll.addView(twotext_buybutton(this,cs,"Offhand:","None",Shopping_code.SHOP_OFFHAND));
        ll.addView(horizontal_line());
        if (cs.armor!=null){
        	ll.addView(text_image_buybutton(this,cs,"Armor:",cs.armor.image,Shopping_code.SHOP_CHEST));
        	ll.addView(twotext(this, cs.armor.name(), cs.armor.description()));
        } else
        	ll.addView(twotext_buybutton(this,cs,"Armor:","None",Shopping_code.SHOP_CHEST));
        ll.addView(horizontal_line());
    	ll.addView(heading(this,"Other items:"));
        if (cs.trinkets.size()>0){
	        if (cs.trinkets.size()>0 && cs.trinkets.get(0)!=null){
	        	ll.addView(onetext_dropbutton(this,cs,0));
	        	ll.addView(onetext(this, cs.trinkets.get(0).description()));
	        }
	        if (cs.trinkets.size()>1 && cs.trinkets.get(1)!=null){
	        	ll.addView(onetext_dropbutton(this,cs,1));
	        	ll.addView(onetext(this, cs.trinkets.get(1).description()));
	        }
	        if (cs.trinkets.size()>2 && cs.trinkets.get(2)!=null){
	        	ll.addView(onetext_dropbutton(this,cs,2));
	        	ll.addView(onetext(this, cs.trinkets.get(2).description()));
	        }
	        if (cs.trinkets.size()>3 && cs.trinkets.get(3)!=null){
	        	ll.addView(onetext_dropbutton(this,cs,3));
	        	ll.addView(onetext(this, cs.trinkets.get(3).description()));
	        }
        }
        while (cs.trinkets.contains(null))
        	cs.trinkets.remove(null); // kludge to fix old bug
        boolean is_packrat = cs.master_action_codes.contains(Character_action_code.CA_PACKRAT);
        for (Item it : cs.trinkets)
        	if (it.action_codes().contains(Character_action_code.CA_PACKRAT))
        		is_packrat = true;
        if (cs.trinkets.size()<3 || (cs.trinkets.size()==3 && is_packrat)){
            Button trinket = new Button(this);
            trinket.setText("Equip another item");
            View.OnClickListener myhandler4 = new View.OnClickListener() {
                public void onClick(View v) {
                	trinket_dialog();
                }
              };
            trinket.setOnClickListener(myhandler4);
        	ll.addView(trinket);
        }
        ll.addView(heading(this,"Potions"));
        for (Potion_type pt : cs.potions){
        	Character_action a = Campaignstate.ca.make_action(pt.get_character_action_code());
        	ll.addView(image_onetext(this,pt.get_image(),a.name()));
        }
        boolean is_apothecary = cs.master_action_codes.contains(Character_action_code.CA_APOTHECARY);
        for (Item it : cs.trinkets)
        	if (it.action_codes().contains(Character_action_code.CA_APOTHECARY))
        		is_apothecary = true;
        if (cs.potions.size()<3 || (cs.potions.size()==3 && is_apothecary)){
            Button pb_shown = new Button(this);
            pb_shown.setText("Buy another potion");
            View.OnClickListener myhandler3 = new View.OnClickListener() {
                public void onClick(View v) {
                	alchemist_dialog();
                }
              };
            pb_shown.setOnClickListener(myhandler3);
        	ll.addView(pb_shown);
        }
	}

	class RestatListener implements View.OnClickListener {
    	CharsheetDialog dlg;
    	public RestatListener(CharsheetDialog _dlg, Charsheet _cs){
    		super();
    		dlg = _dlg;
    		cs = _cs;
    	}
        public void onClick(View v) {
        	AlertDialog.Builder builder = new AlertDialog.Builder(dlg);
        	builder.setTitle("Really upgrade?");
      		builder.setMessage("Do you want to spend your upgrade reward on this character?\n\nIf you say OK, they will disappear and reappear in the Inn, ready to be rebuilt with 23 points. Their equipment will go to your storeroom.");
        	builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
        	    public void onClick(DialogInterface dialog, int which) {
        	    	String min_stat = "";
        	    	int min_stat_value = 0;
    	    		if (cs.constitution>=cs.stat1 && cs.constitution>=cs.stat2 && cs.constitution>=cs.intelligence && cs.constitution>=cs.reflexes && cs.constitution>=cs.stamina){
    	    			min_stat="constitution";
    	    			min_stat_value=cs.constitution;
    	    		}
    	    		if (cs.reflexes>=cs.stat1 && cs.reflexes>=cs.stat2 && cs.reflexes>=cs.intelligence && cs.reflexes>=cs.constitution && cs.reflexes>=cs.stamina){
    	    			min_stat="reflexes";
    	    			min_stat_value=cs.reflexes;
    	    		}
    	    		if (cs.intelligence>=cs.stat1 && cs.intelligence>=cs.stat2 && cs.intelligence>=cs.constitution && cs.intelligence>=cs.reflexes && cs.intelligence>=cs.stamina){
    	    			min_stat="training";
    	    			min_stat_value=cs.intelligence;
    	    		}
    	    		if (cs.stamina>=cs.stat1 && cs.stamina>=cs.stat2 && cs.stamina>=cs.intelligence && cs.stamina>=cs.reflexes && cs.stamina>=cs.constitution){
    	    			min_stat="stamina";
    	    			min_stat_value=cs.stamina;
    	    		}

        	    	if (cs.class_code==Class_code.C_WARRIOR){
        	    		if (cs.stat1>=cs.stat2 && cs.stat1>=cs.constitution && cs.stat1>=cs.intelligence && cs.stat1>=cs.reflexes && cs.stat1>=cs.stamina){
        	    			min_stat="strength";
        	    			min_stat_value=cs.stat1;
        	    		}
        	    		if (cs.stat2>=cs.stat1 && cs.stat2>=cs.constitution && cs.stat2>=cs.intelligence && cs.stat2>=cs.reflexes && cs.stat2>=cs.stamina){
        	    			min_stat="skill";
        	    			min_stat_value=cs.stat2;
        	    		}
        	    	}
        	    	if (cs.class_code==Class_code.C_ROGUE){
        	    		if (cs.stat1>=cs.stat2 && cs.stat1>=cs.constitution && cs.stat1>=cs.intelligence && cs.stat1>=cs.reflexes && cs.stat1>=cs.stamina){
        	    			min_stat="daring";
        	    			min_stat_value=cs.stat1;
        	    		}
        	    		if (cs.stat2>=cs.stat1 && cs.stat2>=cs.constitution && cs.stat2>=cs.intelligence && cs.stat2>=cs.reflexes && cs.stat2>=cs.stamina){
        	    			min_stat="cunning";
        	    			min_stat_value=cs.stat2;
        	    		}
        	    	}
        	    	if (cs.class_code==Class_code.C_PRIEST){
        	    		if (cs.stat1>=cs.stat2 && cs.stat1>=cs.constitution && cs.stat1>=cs.intelligence && cs.stat1>=cs.reflexes && cs.stat1>=cs.stamina){
        	    			min_stat="valor";
        	    			min_stat_value=cs.stat1;
        	    		}
        	    		if (cs.stat2>=cs.stat1 && cs.stat2>=cs.constitution && cs.stat2>=cs.intelligence && cs.stat2>=cs.reflexes && cs.stat2>=cs.stamina){
        	    			min_stat="wisdom";
        	    			min_stat_value=cs.stat2;
        	    		}
        	    	}
        	    	if (cs.class_code==Class_code.C_MAGE){
        	    		if (cs.stat1>=cs.stat2 && cs.stat1>=cs.constitution && cs.stat1>=cs.intelligence && cs.stat1>=cs.reflexes && cs.stat1>=cs.stamina){
        	    			min_stat="power";
        	    			min_stat_value=cs.stat1;
        	    		}
        	    		if (cs.stat2>=cs.stat1 && cs.stat2>=cs.constitution && cs.stat2>=cs.intelligence && cs.stat2>=cs.reflexes && cs.stat2>=cs.stamina){
        	    			min_stat="subtlety";
        	    			min_stat_value=cs.stat2;
        	    		}
        	    	}
					Campaignstate.add_recruit(cs.class_code, cs.image, 0, cs.name, cs.level, 23, min_stat, min_stat_value, 0, 0.0, "Was upgraded as a heroic reward.");
    				if (cs.armor!=null) Campaignstate.items_owned.add(cs.armor);
    				if (cs.offhand!=null) Campaignstate.items_owned.add(cs.offhand);
    				if (cs.melee_weapon!=null) Campaignstate.items_owned.add(cs.melee_weapon);
    				if (cs.missile_weapon!=null) Campaignstate.items_owned.add(cs.missile_weapon);
    				for (Item i : cs.trinkets) Campaignstate.items_owned.add(i);
    				int number = -1;
    				for (int j=0; j<Campaignstate.chars.size(); j++){
    					if (Campaignstate.chars.get(j).equals(cs)){
    						number = j;
    					}
    				}
    				Campaignstate.chars.remove(cs);
    				for (int j=0; j<Campaignstate.current_party.size(); j++){
    					if (Campaignstate.current_party.get(j)==number){
    						Campaignstate.current_party.remove(j);
    					}
    				}
    				for (int j=0; j<Campaignstate.current_party.size(); j++){
    					if (Campaignstate.current_party.get(j)>number)
    						Campaignstate.current_party.set(j, Campaignstate.current_party.get(j) - 1);
    				}
    				Campaignstate.rebuilds = Campaignstate.rebuilds - 1;
    	        	dlg.finish();
    	        	LaunchActivity.dlg.dismiss();
    	        }
        	});
        	builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
        	    public void onClick(DialogInterface dialog, int which) {
        	        dialog.cancel();
        	    }
        	});
        	builder.show();
        }
	}

	class NameListener implements View.OnClickListener {
    	CharsheetDialog dlg;
    	public NameListener(CharsheetDialog _dlg, Charsheet _cs){
    		super();
    		dlg = _dlg;
    		cs = _cs;
    	}
        public void onClick(View v) {
        	AlertDialog.Builder builder = new AlertDialog.Builder(dlg);
        	builder.setTitle("New name");
        	final EditText input = new EditText(dlg);
        	input.setInputType(InputType.TYPE_CLASS_TEXT);
        	builder.setView(input);
        	builder.setPositiveButton("OK", new DialogInterface.OnClickListener() {
        	    public void onClick(DialogInterface dialog, int which) {
        	    	String result = input.getText().toString();
        	    	if (result.length()>0){
        	    		cs.name = result;
	    	        	dlg.finish();
	    	        	LaunchActivity.tv.setText("Your gold: " + Campaignstate.gold);
	    	        	LaunchActivity.tv.invalidate();
	    	        	LaunchActivity.dlg.dismiss();
        	    	}
    	        }
        	});
        	builder.setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
        	    public void onClick(DialogInterface dialog, int which) {
        	        dialog.cancel();
        	    }
        	});
        	builder.show();
        }
      };

    class EndListener implements View.OnClickListener {
    	CharsheetDialog dlg;
    	public EndListener(CharsheetDialog _dlg){
    		super();
    		dlg = _dlg;
    	}
    	public void onClick(View v) {
    		dlg.finish();
		}
    }

    static View onetext(Context context, String txt){
        TextView t = new TextView(context);
        t.setText(txt);
        return t;
    }

    static View onetext(Context context, int txt){
        return onetext(context,Integer.toString(txt));
    }

    static View onetext_italic(Context context, String txt){
        TextView t = new TextView(context);
        t.setText(txt);
        t.setTypeface(t.getTypeface(), Typeface.ITALIC);
        return t;
    }

    static View heading(Context context, String txt){
        TextView head1 = new TextView(context);
        head1.setText(txt);
        head1.setTypeface(head1.getTypeface(), Typeface.BOLD);
        LinearLayout.LayoutParams llp = new LinearLayout.LayoutParams(LayoutParams.WRAP_CONTENT, LayoutParams.WRAP_CONTENT);
        llp.setMargins(0, 16, 0, 0);
        head1.setLayoutParams(llp);
        return head1;
    }

    static View twotext_firstitalic(Context context,String txt1,String txt2){
        LinearLayout row1 = new LinearLayout(context);
        row1.setBackgroundColor(Color.argb(0,0,0,0));
        row1.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.WRAP_CONTENT));
        row1.setOrientation(LinearLayout.HORIZONTAL);
        row1.setGravity(Gravity.LEFT);
        TextView item1 = new TextView(context);
        item1.setText(txt1);
        item1.setWidth(140);
        item1.setTypeface(item1.getTypeface(), Typeface.ITALIC);
        row1.addView(item1);
        TextView item2 = new TextView(context);
        item2.setText(txt2);
        row1.addView(item2);
        return row1;
    }

    static View twotext(Context context,String txt1,String txt2){
        LinearLayout row1 = new LinearLayout(context);
        row1.setBackgroundColor(Color.argb(0,0,0,0));
        row1.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.WRAP_CONTENT));
        row1.setOrientation(LinearLayout.HORIZONTAL);
        row1.setGravity(Gravity.LEFT);
        TextView item1 = new TextView(context);
        item1.setText(txt1);
        item1.setWidth(140);
        row1.addView(item1);
        TextView item2 = new TextView(context);
        item2.setText(txt2);
        row1.addView(item2);
        return row1;
    }

    View image_onetext(Context context,String image,String text){
        RelativeLayout row1 = new RelativeLayout(context);
        row1.setBackgroundColor(Color.argb(0,0,0,0));
	    RelativeLayout.LayoutParams left = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    left.addRule(RelativeLayout.CENTER_VERTICAL);
	    left.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
        ImageView item1 = new ImageView(context);
        item1.setBackgroundDrawable(new BitmapDrawable(this.getResources(),LaunchActivity.gi.getImageBasic(image)));
        row1.addView(item1,left);
        item1.setId(40000);
	    RelativeLayout.LayoutParams midleft = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    midleft.addRule(RelativeLayout.CENTER_VERTICAL);
	    midleft.addRule(RelativeLayout.RIGHT_OF, item1.getId());
        TextView item2 = new TextView(context);
        item2.setText(text);
        item2.setWidth(140);
        row1.addView(item2,midleft);
        return row1;
    }

    View text_image_buybutton(Context context,Charsheet cs,String txt,String image,Shopping_code slot){
        RelativeLayout row1 = new RelativeLayout(context);
        row1.setBackgroundColor(Color.argb(0,0,0,0));
	    RelativeLayout.LayoutParams left = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    left.addRule(RelativeLayout.CENTER_VERTICAL);
	    left.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
        TextView item1 = new TextView(context);
        item1.setText(txt);
        item1.setWidth(140);
        row1.addView(item1,left);
        item1.setId(20000);
	    RelativeLayout.LayoutParams midleft = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    midleft.addRule(RelativeLayout.CENTER_VERTICAL);
	    midleft.addRule(RelativeLayout.RIGHT_OF, item1.getId());
        ImageView item2 = new ImageView(context);
        item2.setBackgroundDrawable(new BitmapDrawable(this.getResources(),LaunchActivity.gi.getImageBasic(image)));
        row1.addView(item2,midleft);
	    RelativeLayout.LayoutParams right = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    right.addRule(RelativeLayout.CENTER_VERTICAL);
	    right.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
        BuyButton item3 = new BuyButton(cs,slot);
        row1.addView(item3,right);
        item3.setId(20001);
	    RelativeLayout.LayoutParams midright = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    midright.addRule(RelativeLayout.CENTER_VERTICAL);
	    midright.addRule(RelativeLayout.LEFT_OF, item3.getId());
	    SwapButton item4 = new SwapButton(cs,slot);
        row1.addView(item4,midright);
        return row1;
    }

    View horizontal_line(){
    	View v = new View(this);
    	LinearLayout.LayoutParams viewLp = new LayoutParams(LayoutParams.MATCH_PARENT, 1);
    	viewLp.setMargins(0,5,0,5);
    	v.setLayoutParams(viewLp);
    	v.setBackgroundColor(Color.WHITE);
    	return v;
    }

    View twotext_buybutton(Context context,Charsheet cs,String txt1,String txt2,Shopping_code slot){
        RelativeLayout row1 = new RelativeLayout(context);
        row1.setBackgroundColor(Color.argb(0,0,0,0));
	    RelativeLayout.LayoutParams left = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    left.addRule(RelativeLayout.CENTER_VERTICAL);
	    left.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
        TextView item1 = new TextView(context);
        item1.setText(txt1);
        item1.setWidth(140);
        row1.addView(item1,left);
        item1.setId(20000);
	    RelativeLayout.LayoutParams midleft = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    midleft.addRule(RelativeLayout.CENTER_VERTICAL);
	    midleft.addRule(RelativeLayout.RIGHT_OF, item1.getId());
        TextView item2 = new TextView(context);
        item2.setText(txt2);
        item2.setWidth(140);
        row1.addView(item2,midleft);
	    RelativeLayout.LayoutParams right = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    right.addRule(RelativeLayout.CENTER_VERTICAL);
	    right.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
        BuyButton item3 = new BuyButton(cs,slot);
        row1.addView(item3,right);
        item3.setId(20001);
	    RelativeLayout.LayoutParams midright = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    midright.addRule(RelativeLayout.CENTER_VERTICAL);
	    midright.addRule(RelativeLayout.LEFT_OF, item3.getId());
	    SwapButton item4 = new SwapButton(cs,slot);
        row1.addView(item4,midright);
        return row1;
    }

    View onetext_dropbutton(Context context,Charsheet cs,int trinket_no){
    	Item trinket = cs.trinkets.get(trinket_no);
        RelativeLayout row1 = new RelativeLayout(context);
        row1.setBackgroundColor(Color.argb(0,0,0,0));
	    RelativeLayout.LayoutParams left = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    left.addRule(RelativeLayout.CENTER_VERTICAL);
	    left.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
        TextView item1 = new TextView(context);
        item1.setText(trinket.name());
        item1.setWidth(300);
        row1.addView(item1,left);
	    RelativeLayout.LayoutParams right = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
	    right.addRule(RelativeLayout.CENTER_VERTICAL);
	    right.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
        DropTrinketButton item2 = new DropTrinketButton(trinket_no);
        row1.addView(item2,right);
        return row1;
    }

    class BuyButton extends Button {
    	public BuyButton(Charsheet cs,Shopping_code slot){
    		super(CharsheetDialog.this);
    		setText("Buy");
            setOnClickListener(new BuyListener(slot));
    	}
        class BuyListener implements View.OnClickListener {
        	Shopping_code slot;
        	public BuyListener(Shopping_code _slot){
        		super();
        		slot = _slot;
        	}
        	public void onClick(View v) {
        		buy_dialog(slot);
    		}
        }
    }

    class SwapButton extends Button {
    	public SwapButton(Charsheet cs,Shopping_code slot){
    		super(CharsheetDialog.this);
    		setText("Swap");
            setOnClickListener(new SwapListener(slot));
    	}
        class SwapListener implements View.OnClickListener {
        	Shopping_code slot;
        	public SwapListener(Shopping_code _slot){
        		super();
        		slot = _slot;
        	}
        	public void onClick(View v) {
        		swap_dialog(slot);
    		}
        }
    }

    class DropTrinketButton extends Button {
    	public DropTrinketButton(int trinket_no){
    		super(CharsheetDialog.this);
    		setText("Drop");
            setOnClickListener(new DropTrinketListener(trinket_no));
    	}
        class DropTrinketListener implements View.OnClickListener {
        	int trinket_no;
        	public DropTrinketListener(int _trinket_no){
        		super();
        		trinket_no = _trinket_no;
        	}
        	public void onClick(View v) {
        		make_ll(null,null,false,null,trinket_no);
            	scroll.invalidate();
            	scroll.postInvalidate();
            }
        }
    }

    static View twotext(Context context,String txt1,int txt2){
    	return twotext(context,txt1,Integer.toString(txt2));
    }

    static double round_to_1_dp(double x){
        return Math.round(x*10.0)/10.0;
    }

    static double round_to_2_dp(double x){
        return Math.round(x*100.0)/100.0;
    }

    static AlertDialog bd_shown, ld_shown, pd_shown, sd_shown, td_shown;

	void alchemist_dialog(){
        AlertDialog.Builder builder = new AlertDialog.Builder(this);
        ScrollView sv = new ScrollView(this);
        sv.setBackgroundColor(Color.argb(0,0,0,0));
        sv.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.MATCH_PARENT));
        LinearLayout lld = new LinearLayout(this);
        lld.setBackgroundColor(Color.BLACK);
        lld.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.WRAP_CONTENT));
        lld.setOrientation(LinearLayout.VERTICAL);
        lld.setGravity(Gravity.TOP);
        ArrayList<PotionListener> listeners = new ArrayList<PotionListener>();
        ArrayList<Potion_type> eligible = new ArrayList<Potion_type>();
        for (Potion_type pc : Potion_type.values()){
        	Character_action pca = Campaignstate.ca.make_action(pc.get_character_action_code());
			int cost = pca.gold_cost();
			if (Campaignstate.victories.contains(Scenario_code.SC_DESERT)) cost=cost/5;
        	if (Campaignstate.gold < cost)
        		continue;
        	if (cs.class_code==Class_code.C_MAGE && !pca.mage_ok())
        		continue;
        	if (cs.class_code==Class_code.C_PRIEST && !pca.priest_ok())
        		continue;
        	if (cs.class_code==Class_code.C_ROGUE && !pca.rogue_ok())
        		continue;
        	if (cs.class_code==Class_code.C_WARRIOR && !pca.warrior_ok())
        		continue;
        	if (cs.level < pc.get_min_level())
        		continue;
        	eligible.add(pc);
        }
        Collections.sort(eligible,new Comparator<Potion_type>(){public int compare(Potion_type lhs, Potion_type rhs){Character_action lhs_a = Campaignstate.ca.make_action(lhs.get_character_action_code()), rhs_a=Campaignstate.ca.make_action(rhs.get_character_action_code()); return rhs_a.gold_cost().compareTo(lhs_a.gold_cost());}});
        for (Potion_type pc : eligible){
        	String name, description;
			Character_action pca = Campaignstate.ca.make_action(pc.get_character_action_code());
			int cost = pca.gold_cost();
			if (Campaignstate.victories.contains(Scenario_code.SC_DESERT)) cost=cost/5;
			if (cs.master_action_codes.contains(Character_action_code.CA_HAGGLER)) cost = (cost*3)/5;
			if (cost<1) cost=1;
        	name = pca.name() + " (" + cost + ")";
        	description = pca.out_of_game_description();
			ChoiceButton sb = new ChoiceButton(this,name,description,pc.get_image(),"Buy",false);
			PotionListener thislistener = new PotionListener(pc);
		    listeners.add(thislistener);
    		sb.DoIt.setOnClickListener(thislistener);
			lld.addView(sb);
        }
        if (listeners.size()==0){
        	LaunchActivity.playSound("cancel");
        	notify(CharsheetDialog.this, "gold", "You have not the gold!", "The alchemist throws you out of his shop.");
        	return;
        }
        sv.addView(lld);
        String title;
        if (Campaignstate.victories.contains(Scenario_code.SC_DESERT)) title="The alchemist is friendly";
        else title="At the alchemist's shop";
        builder.setTitle(title)
        .setCancelable(true)
        .setView(sv)
        .setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
        	public void onClick(DialogInterface dialog, int id) {
        		dialog.cancel();}});
        pd_shown = builder.create();
        pd_shown.show();
	}

    class PotionListener implements View.OnClickListener {
    	Potion_type this_p;

    	public PotionListener(Potion_type _p){
    		this_p = _p;
    	}

    	public void onClick(View v) {
        	pd_shown.dismiss();
        	make_ll(null,null,false,this_p,null);
        	scroll.invalidate();
        	scroll.postInvalidate();
        }
      };

  	void buy_dialog(Shopping_code slot){
        AlertDialog.Builder builder = new AlertDialog.Builder(this);
        ScrollView sv = new ScrollView(this);
        sv.setBackgroundColor(Color.argb(0,0,0,0));
        sv.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.MATCH_PARENT));
        LinearLayout lld = new LinearLayout(this);
        lld.setBackgroundColor(Color.BLACK);
        lld.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.WRAP_CONTENT));
        lld.setOrientation(LinearLayout.VERTICAL);
        lld.setGravity(Gravity.TOP);
        ArrayList<BuyListener> listeners = new ArrayList<BuyListener>();
        ArrayList<Item> eligible = new ArrayList<Item>();
        for (Equipment_type_code ec : Equipment_type_code.values()){
        	Item i = Campaignstate.i.make_item(ec);
        	boolean right_slot = false;
        	if (slot==Shopping_code.SHOP_MAINHAND && i.is_melee_weapon())
        		right_slot=true;
        	if (slot==Shopping_code.SHOP_OFFHAND && i.is_offhand())
        		right_slot=true;
        	if (slot==Shopping_code.SHOP_SHOOTER && i.is_missile_weapon())
        		right_slot=true;
        	if (slot==Shopping_code.SHOP_CHEST && i.is_armor())
        		right_slot=true;
        	if (slot==Shopping_code.SHOP_OFFHAND && cs.melee_weapon!=null && cs.melee_weapon.two_handed())
        		continue;
        	if (!right_slot || i.cost()==0)
        		continue;
        	if (i.cost()>=10000)
        		continue; // this is a dummy value
        	if (!cs.can_use(i))
        		continue;
        	if (Campaignstate.gold < i.cost())
        		continue;
        	eligible.add(i);
        }
        Collections.sort(eligible,new Comparator<Item>(){public int compare(Item lhs, Item rhs){return rhs.cost().compareTo(lhs.cost());}});
        for (Item i : eligible){
        	String name, description;
        	name = i.name() + " (" + i.cost() + ")";
        	description = i.description();
			ChoiceButton sb = new ChoiceButton(this,name,description,i.image,"Buy",false);
			BuyListener thislistener = new BuyListener(i);
		    listeners.add(thislistener);
    		sb.DoIt.setOnClickListener(thislistener);
			lld.addView(sb);
        }
        if (listeners.size()==0){
        	LaunchActivity.playSound("cancel");
        	notify(CharsheetDialog.this, null, "Nothing to use!", "There is nothing you can get in that slot.");
        	return;
        }
        sv.addView(lld);
        builder.setTitle("Shopping")
        .setCancelable(true)
        .setView(sv)
        .setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
        	public void onClick(DialogInterface dialog, int id) {
        		dialog.cancel();}});
        bd_shown = builder.create();
        bd_shown.show();
	}

    class BuyListener implements View.OnClickListener {

    	Item this_i;

    	public BuyListener(Item _i){
    		this_i = _i;
    	}

    	public void onClick(View v) {
        	bd_shown.dismiss();
        	make_ll(null,this_i,false,null,null);
        	scroll.invalidate();
        	scroll.postInvalidate();
        }
      };

  	void swap_dialog(Shopping_code slot){
        AlertDialog.Builder builder = new AlertDialog.Builder(this);
        ScrollView sv = new ScrollView(this);
        sv.setBackgroundColor(Color.argb(0,0,0,0));
        sv.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.MATCH_PARENT));
        LinearLayout lld = new LinearLayout(this);
        lld.setBackgroundColor(Color.BLACK);
        lld.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.WRAP_CONTENT));
        lld.setOrientation(LinearLayout.VERTICAL);
        lld.setGravity(Gravity.TOP);
        ArrayList<SwapListener> listeners = new ArrayList<SwapListener>();
        ArrayList<Item> eligible = new ArrayList<Item>();
        for (Item i : Campaignstate.items_owned){
        	if (i==null)
        		continue;
        	boolean right_slot = false;
        	if (slot==Shopping_code.SHOP_MAINHAND && i.is_melee_weapon())
        		right_slot=true;
        	if (slot==Shopping_code.SHOP_OFFHAND && i.is_offhand())
        		right_slot=true;
        	if (slot==Shopping_code.SHOP_SHOOTER && i.is_missile_weapon())
        		right_slot=true;
        	if (slot==Shopping_code.SHOP_CHEST && i.is_armor())
        		right_slot=true;
        	if (!right_slot)
        		continue;
        	if (slot==Shopping_code.SHOP_OFFHAND && cs.melee_weapon!=null && cs.melee_weapon.two_handed())
        		continue;
        	if (!cs.can_use(i))
        		continue;
        	boolean already = false;
        	for (int count=0; count<eligible.size(); count++){
        		Item i2 = eligible.get(count);
        		if (i.getClass()==i2.getClass()){
        			already = true;
        			break;
        		}
        	}
        	if (!already){
        		eligible.add(i);
        	}
        }
        Collections.sort(eligible,new Comparator<Item>(){public int compare(Item lhs, Item rhs){return rhs.cost().compareTo(lhs.cost());}});
        for (int count=0; count<eligible.size(); count++){
        	Item i = eligible.get(count);
        	String name, description;
        	int n_of = 0;
        	for (Item i2 : Campaignstate.items_owned){
        		if (i.getClass()==i2.getClass()){
        			n_of = n_of + 1;
        		}
        	}
			if (n_of>1){
				name = (i.name() + " (" + n_of + ")");
			} else {
				name = (i.name());
			}
			description = i.description();
			ChoiceButton sb = new ChoiceButton(this,name,description,i.image,"Use",false);
			SwapListener thislistener = new SwapListener(i);
		    listeners.add(thislistener);
    		sb.DoIt.setOnClickListener(thislistener);
			lld.addView(sb);
        }
        if (listeners.size()==0){
        	LaunchActivity.playSound("cancel");
        	notify(CharsheetDialog.this, null, "Nothing to use!", "There is nothing you can use in that slot.");
        	return;
        }
        sv.addView(lld);
        builder.setTitle("Swap equipment")
        .setCancelable(true)
        .setView(sv)
        .setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
        	public void onClick(DialogInterface dialog, int id) {
        		dialog.cancel();}});
        sd_shown = builder.create();
        sd_shown.show();
	}

    class SwapListener implements View.OnClickListener {

    	Item this_i;

    	public SwapListener(Item _i){
    		this_i = _i;
    	}

    	public void onClick(View v) {
        	sd_shown.dismiss();
        	make_ll(null,this_i,true,null,null);
        	scroll.invalidate();
        	scroll.postInvalidate();
        }
      };

  	void trinket_dialog(){
        AlertDialog.Builder builder = new AlertDialog.Builder(this);
        ScrollView sv = new ScrollView(this);
        sv.setBackgroundColor(Color.argb(0,0,0,0));
        sv.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.MATCH_PARENT));
        LinearLayout lld = new LinearLayout(this);
        lld.setBackgroundColor(Color.BLACK);
        lld.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.WRAP_CONTENT));
        lld.setOrientation(LinearLayout.VERTICAL);
        lld.setGravity(Gravity.TOP);
        ArrayList<TrinketListener> listeners = new ArrayList<TrinketListener>();
        ArrayList<Item> eligible = new ArrayList<Item>();
        ArrayList<Integer> n_of = new ArrayList<Integer>();
        for (Item i : Campaignstate.items_owned){
        	if (i==null)
        		continue;
        	if (!i.is_trinket())
        		continue;
        	if (!cs.can_use(i))
        		continue;
        	if (i.trinket_type()==Trinket_type_code.TR_ARROWS){
        		if (!(cs.missile_weapon!=null && cs.missile_weapon.takes_arrows())){
        			continue;
        		}
        	}
        	boolean already = false;
        	for (int count=0; count<eligible.size(); count++){
        		Item i2 = eligible.get(count);
        		if (i.getClass()==i2.getClass()){
        			already = true;
        			n_of.set(count, n_of.get(count)+1);
        		}
        	}
        	for (Item i3 : cs.trinkets){
        		if (i.getClass()==i3.getClass()){
        			already = true;
        		}
        	}
        	if (already)
        		continue;
        	eligible.add(i);
        	n_of.add(1);
        }
        Collections.sort(eligible,new Comparator<Item>(){public int compare(Item lhs, Item rhs){return rhs.cost().compareTo(lhs.cost());}});
        for (int count=0; count<eligible.size(); count++){
        	Item i = eligible.get(count);
        	String name, description;
			if (n_of.get(count)>1){
				name = (i.name() + " (" + n_of.get(count) + ")");
			} else {
				name = (i.name());
			}
			description = i.description();
			ChoiceButton sb = new ChoiceButton(this,name,description,null,"Use",false);
			TrinketListener thislistener = new TrinketListener(i);
		    listeners.add(thislistener);
    		sb.DoIt.setOnClickListener(thislistener);
			lld.addView(sb);
        }
        if (listeners.size()==0){
        	LaunchActivity.playSound("cancel");
        	notify(CharsheetDialog.this, null, "Nothing to use!", "Your party does not have any spare items that could be used in that slot.");
        	return;
        }
        sv.addView(lld);
        builder.setTitle("Use an item")
        .setCancelable(true)
        .setView(sv)
        .setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
        	public void onClick(DialogInterface dialog, int id) {
        		dialog.cancel();}});
        td_shown = builder.create();
        td_shown.show();
	}

    class TrinketListener implements View.OnClickListener {

    	Item this_i;

    	public TrinketListener(Item _i){
    		this_i = _i;
    	}

    	public void onClick(View v) {
        	td_shown.dismiss();
        	make_ll(null,this_i,true,null,null);
        	scroll.invalidate();
        	scroll.postInvalidate();
        }
      };

    void learn_dialog(){
        AlertDialog.Builder builder = new AlertDialog.Builder(this);
        ScrollView sv = new ScrollView(this);
        sv.setBackgroundColor(Color.argb(0,0,0,0));
        sv.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.MATCH_PARENT));
        LinearLayout lld = new LinearLayout(this);
        lld.setBackgroundColor(Color.BLACK);
        lld.setLayoutParams(new LayoutParams(LayoutParams.MATCH_PARENT,LayoutParams.WRAP_CONTENT));
        lld.setOrientation(LinearLayout.VERTICAL);
        lld.setGravity(Gravity.TOP);
        ArrayList<Character_action_code> eligible = new ArrayList<Character_action_code>();
        for (Character_action_code ca : Character_action_code.values()){
        	if (cs.meets_requirements(ca)){
        		Character_action a = Campaignstate.ca.make_action(ca);
        		if (a.never_learnable())
        			continue;
        		eligible.add(ca);
        	}
        }
        Collections.sort(eligible,new Comparator<Character_action_code>(){public int compare(Character_action_code lhs, Character_action_code rhs){
            Character_action rhs_action=Campaignstate.ca.make_action(rhs);
            Character_action lhs_action=Campaignstate.ca.make_action(lhs);
            return lhs_action.name().compareTo(rhs_action.name());}});
        ArrayList<LearnListener> listeners = new ArrayList<LearnListener>();
        for (Character_action_code ca : eligible){
    		Character_action a = Campaignstate.ca.make_action(ca);
    		String text = a.name();
    		if (a.recommended() & Campaignstate.max_char_level()<=5){
    			text = text + " (recommended)";}
    		ChoiceButton sb = new ChoiceButton(this,text,a.out_of_game_description(),null,"Learn",a.recommended() & Campaignstate.max_char_level()<=5);
    		LearnListener thislistener = new LearnListener(ca);
            listeners.add(thislistener);
    		sb.DoIt.setOnClickListener(thislistener);
    		lld.addView(sb);
        }
        sv.addView(lld);
        builder.setTitle(cs.name + " - Learning a new skill")
        .setIcon(new BitmapDrawable(this.getResources(),LaunchActivity.gi.getImageBasic(cs.image)))
        .setCancelable(true)
        .setView(sv)
        .setNegativeButton("Cancel", new DialogInterface.OnClickListener() {
        	public void onClick(DialogInterface dialog, int id) {
        		dialog.cancel();}});
        ld_shown = builder.create();
        ld_shown.show();
     }


    class ChoiceButton extends RelativeLayout {
		Button DoIt;

    	public ChoiceButton(Context context, String name, String description, String image, String verb, boolean highlight) {
			super(context);
    		setBackgroundColor(Color.WHITE);
            LinearLayout.LayoutParams all = new LinearLayout.LayoutParams(LinearLayout.LayoutParams.MATCH_PARENT, LinearLayout.LayoutParams.WRAP_CONTENT);
            all.setMargins(1,2,2,1);
            setLayoutParams(all);
    	    ImageView item0 = new ImageView(context);
    	    int mid_width = 250;
    	    if (image!=null && image!=""){
                RelativeLayout.LayoutParams leftest = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
        	    leftest.addRule(RelativeLayout.CENTER_VERTICAL);
        	    leftest.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
	    	    item0.setBackgroundDrawable(new BitmapDrawable(this.getResources(),LaunchActivity.gi.getImageBasic(image)));
	            addView(item0,leftest);
	    	    item0.setId(19999);
    	    } else {
    	    	mid_width = mid_width + 80;
    	    }
            RelativeLayout.LayoutParams left = new RelativeLayout.LayoutParams(mid_width, RelativeLayout.LayoutParams.WRAP_CONTENT);
    	    left.addRule(RelativeLayout.ALIGN_PARENT_TOP);
    	    if (image!=null && image!=""){
    	    	left.addRule(RelativeLayout.RIGHT_OF, item0.getId());
    	    } else {
    	    	left.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
    	    }
    	    TextView item1 = new TextView(context);
    	    item1.setText(name);
    	    if (highlight) item1.setTextColor(Color.RED);
    	    	else item1.setTextColor(Color.BLACK);
    	    item1.setTypeface(item1.getTypeface(), Typeface.BOLD);
            addView(item1,left);
    	    item1.setId(20000);
    	    RelativeLayout.LayoutParams below = new RelativeLayout.LayoutParams(mid_width, RelativeLayout.LayoutParams.WRAP_CONTENT);
    	    if (image!=null && image!=""){
    	    	below.addRule(RelativeLayout.RIGHT_OF, item0.getId());
    	    } else {
    	    	below.addRule(RelativeLayout.ALIGN_PARENT_LEFT);
    	    }
    	    below.addRule(RelativeLayout.BELOW, item1.getId());
    	    TextView item2 = new TextView(context);
    	    item2.setText(description);
    	    item2.setTextColor(Color.BLACK);
    	    item2.setWidth(310);
    	    addView(item2,below);
    	    RelativeLayout.LayoutParams right = new RelativeLayout.LayoutParams(RelativeLayout.LayoutParams.WRAP_CONTENT, RelativeLayout.LayoutParams.WRAP_CONTENT);
    	    right.addRule(RelativeLayout.CENTER_VERTICAL);
    	    right.addRule(RelativeLayout.ALIGN_PARENT_RIGHT);
    	    DoIt = new Button(context);
    	    DoIt.setText(verb);
    	    addView(DoIt,right);
		}
    }

    class LearnListener implements View.OnClickListener {

    	Character_action_code this_ca;

    	public LearnListener(Character_action_code _ca){
    		this_ca = _ca;
    	}

    	public void onClick(View v) {
        	ld_shown.dismiss();
        	make_ll(this_ca,null,false,null,null);
        	scroll.invalidate();
        	scroll.postInvalidate();
        }
      };

     static void notify(Context c, String image, String title, String text){
  		AlertDialog alertDialog = new AlertDialog.Builder(c).create();
  		alertDialog.setTitle(title);
  		alertDialog.setMessage(text);
  		if (image!=null)
  			alertDialog.setIcon(new BitmapDrawable(LaunchActivity.gi.getImageBasic(image)));
  		alertDialog.setButton("OK", new DialogInterface.OnClickListener() {
  		   public void onClick(DialogInterface dialog, int which) {
  		      dialog.cancel();}
  		});
  		alertDialog.show();
     }

}

